home *** CD-ROM | disk | FTP | other *** search
Text File | 2000-05-27 | 111.4 KB | 2,413 lines |
-
- Speak Freely for Unix
- (formerly netfone)
-
- Development Log
- by John Walker
- http://www.fourmilab.ch/
-
- 26 August 1995
-
- John Gilmore encountered an undefined symbol irint when building on
- SunOS 4.1.3_U1. Apparently this function, which is part of the main C
- library in 4.1.1, was moved somewhere else in 4.1.3. To put an end of
- this irint() nonsense once and for all, I rewrote the expression in
- soundbyte.c to eliminate the call to irint() entirely.
-
- John also suggested making the distribution tar extract into a
- netfone-<version> directory as most GNU packages do. Starting with
- release 5.1, which will extract into a netfone-5.1 directory, that's
- how it'll be.
-
- 29 August 1995
-
- Added logic to mike to calculate the precise number of samples which
- will fit in a sound buffer to optimally fill a single UDP packet.
- John Gilmore pointed out that sending lots of individual packets on
- our own is actually more efficient than forcing the network driver to
- break large packets into fragments. It also reduces the sound delay,
- since we don't have to wait for a large sound buffer to be filled
- before getting it on it's way to the other end.
-
- Note that even though mike will now never send a packet larger than
- 512 bytes, speaker continues to be able to handle packets with as
- many as 8000 samples and thus remains compatible with older versions of
- mike.
-
- 31 August 1995
-
- Added -d and -q switches to speaker which, if specified, override the
- debug mode specified in incoming packets. The -d switch is
- particularly handy when you want to log every packet and don't have
- control over the sending end. The -q switch allows running speaker in
- the background without worrying about where the output is going to go
- is somebody starts sending with debug mode on.
-
- To reduce network traffic and improve conference call performance,
- I made push-to-talk (-b) mode the default in mike. Continuous
- transmission (unless squelched) is selected with the -a switch.
-
- 1 September 1995
-
- Added ADPCM compression to mike (enabled by the -f switch) and decompression
- to speaker. ADPCM halves the number of bytes in a packet without substantial
- degradation of voice-grade audio, far less than that of the -c switch,
- which achieves the same degree of compression. You can specify -c
- and -f together for a 4x reduction in bandwidth, with substantial loss
- of quality. ADPCM and GSM compression cannot be used simultaneously.
-
- ADPCM compression is provided primarily as an alternative to Simple
- (-c) compression for users with a 64 Kb connection who don't have a
- fast enough CPU to run GSM. ADPCM is much faster on both compression and
- decompression than GSM.
-
- 2 September 1995
-
- Release 5.1.
-
- 15 September 1995
-
- Implemented a crude but better-than-nothing "answering machine" in
- speaker. Specifying the "-rfile" option records all sound received
- in the named file in Sun .au format (including header). If you
- specify "-r+file" the sound is appended to the named file if it
- exists. As with a real answering machine with the volume turned up,
- the sound is still played. Obviously there are a zillion nice things
- that one can immediately think of which would improve this feature,
- but at least it provides a stopgap which captures attempts to
- communicate while you were away from the machine.
-
- 17 September 1995
-
- Discovered that a "quick fix" in the SGI audio input soundgrab()
- function in soundbyte.c was violating the maximum packet size for
- memory-constrained versions of WINSOCK. Fixing that was
- straightforward, but I ran squarely into a bug where we'd hang trying
- to flush queued input when transitioning to talk mode in push-to-talk.
- I added a new soundflush() function dedicated to flushing the input
- queue (however that is accomplished) and provided Sun and SGI
- implementations of this function.
-
- Lots of little changes all over to transition the package name from
- Netfone to Speak Freely for Unix. Much more remains to be done,
- particularly separating the option sections for sfmike and sfspeaker
- in the man page.
-
- 19 September 1995
-
- Finished changes to programs, Makefile, and manual page for renaming
- to Speak Freely for Unix.
-
- Version 5.2 released.
-
- 20 September 1995
-
- Added time and date to the "connect" and "idle" messages produced by
- the -v option on sfspeaker.
-
- 21 September 1995
-
- Installed the ability to automatically generate, encrypt with PGP, and
- transmit a session key to the receiving machine. Since PGP is invoked
- to encrypt and decrypt the key, Speak Freely remains free of any RSA
- patent issues; the user simply obtains and installs the correct
- version of PGP and Speak Freely automatically provides public key
- support compatible with PGP. To encrypt sound to one or more people
- with a public key, use the:
-
- -z"user1 user2..."
-
- option on sfmike. The user names are the same as you specify on the
- PGP command line when encrypting files.
-
- On the receiving end, when a PGP-encrypted session key is received,
- PGP is invoked to decrypt it. Decryption requires your RSA private
- key, for which the pass phrase must be provided. By default, PGP
- asks you for the pass phrase each time a session is initiated. You
- can override this by specifying the pass phrase using the PGPPASS
- environment variable (see the PGP documentation for details and a
- discussion of the vulnerability this may create) or by using the
-
- -z"Pass phrase"
-
- option on speaker. The given pass phrase is then passed to PGP with
- its own -z option each time it is invoked.
-
- 23 September 1995
-
- Sfmike didn't accept numeric IP addresses--only resolvable host names.
- Fixed to call inet_addr then only try gethostbyname() if it fails.
-
- Mike.c and speaker.c printed IP addresses the hard way. I changed
- them to use inet_ntoa.
-
- Speaker.c failed to reload the loop variable used when searching for
- an active connection at the start of each search. This could lead
- to segmentation faults after connections had been closed. Fixed.
-
- Connections kept around to preserve their PGP session keys caused the
- 10 second timer not to be canceled after all connections have gone
- idle. Fixed.
-
- Support for half-duplex audio devices. If HALF_DUPLEX is defined
- at compile time, sfmike sends the copy of sfspeaker running on the
- local host a pair of fHalfDuplex messages with the fHalfDuplexMute and
- fHalfDuplexResume bits set. On receiving a fHalfDuplexMute, sfspeaker
- closes the audio device, if open, and sets a flag which causes all
- audio input to be discarded. When fHalfDuplexResume is received,
- audio input is enabled, to be acquired upon receipt of the next sound
- buffer.
-
- Integrated fixes from Andrey A. Chernov to allow compiling for
- FreeBSD, using its Sun-like /dev/audio device.
-
- 24 September 1995
-
- First cut at IP Multicast support. Multicast support is included only
- if IP_ADD_MEMBERSHIP is defined at compile time; we assume that it
- will be defined only on system with mrouted. If multicast is present,
- sfspeaker recognises the "-Mhost/ip" option to indicate one or more
- Multicast groups to which it should add membership. Sound packets
- from any of the named multicast groups as well as those sent directly
- to the bound port will be played.
-
- On the sfmike side, multicast thresholds can be specified by an
- integer after the multicast group name or IP number, delimited by a
- slash. To transmit to a continent-wide multicast group you might use
- the command:
-
- sfmike 230.1.217.11/128
-
- Users who fret over the security risks inherent in the PGPPASS or
- -z"Pass phrase" method of supplying the pass phrase to PGP but can't
- stand having to enter the pass phrase for every new session key now
- have a new option. If you specify "-z" with no pass phrase on the
- call to speaker, it prompts you for the pass phrase once at the start
- of execution, then supplies that phrase to PGP for all subsequent
- connections. Note however that the pass phrase is passed to PGP with
- its -z option, so whatever risk that creates remains present.
-
- Renamed "one-time pad" to "key file" and included a note about its
- cryptographic shortcomings in the manual page.
-
- 25 September 1995
-
- More fixes from Andrey A. Chernov for FreeBSD--the include of
- sys/timeb.hin netfone.h was conditioned on "sun" not "BSD_like",
- soundflush() in soundbyte.c needed to use a read() loop and test
- EAGAIN rather than the Sun-specific FIONREAD ioctl(), and debug output
- from mike.c looks better if cbreak() mode is used rather than raw().
-
- 5 October 1995
-
- Added debug mode output to sfspeaker to indicate when it's off
- calling PGP to decode a session key and whether the process
- succeeded or failed. The long pauses were disturbing when you
- didn't know what was going on.
-
- 6 October 1995
-
- Added the mellifluous new ring.au to the standard release.
-
- Feature release 5.3.
-
- 15 October 1995
-
- Added the "-Pport" option to speaker.c to specify which port it
- listens on. If specified, this overrides the INTERNET_PORT defined in
- the Makefile.
-
- Allowed specification of the port mike.c transmits to as a number
- appended to the hostname or IP address, delimited by a colon. The
- port, if specified, must appear before any multicast scope
- specification. Thus, a multicast address with port and scope
- specified would appear like:
-
- 227.11.133.51:5050/64
-
- 5 November 1995
-
- Finished implementation of Look Who's Listening, with changes in
- speaker.c to notify the server, and new modules lwld.c (the server)
- and lwl.c (the client). The manual pages have been split up into a
- separate page for each program.
-
- Disabled all of the RTP support except that needed for Look Who's
- Listening. It isn't ready for prime time, and there's no reason to
- delay LWL, which everybody is screaming for, to wait for it.
-
- 6 November 1995
-
- Added support for the LPC compression mode (-lpc) included in the RTP
- spec. It's tricky to set up, since any clipping of audio drives it
- absolutely nuts, but 12-to-1 compression is worth the bother if you
- have a slow link. You can enable -lpc and -c at the same time, but
- the result is so poor it's not worth trying.
-
- 7 November 1995
-
- Added an -n option to speaker.c which causes it to ignore any ring
- requests from remote hosts. This is for Sun users who've hooked a
- good sound system up to the audio output jack and get irritated when a
- remote ring switches it back to the built-in speaker.
-
- Feature release 5.5.
-
- 19 November 1995
-
- Integrated fixes for various warning messages from GCC 2.7.0 for
- Solaris reported by Mark B. Hamby. Two of these were legitimate bugs
- in lwl.c and lwld.c, but would actually cause a problem only in the
- extremely unlikely circumstance of malloc() failing on the allocation
- of a small buffer. The rest were just complaints about failure to
- cast pointers to the (char *) defined for some of the socket calls.
-
- I created a new "contrib" directory for third party software that
- is not directly integrated into Speak Freely. The first item is
- "tkshell", a Tcl/Tk/Tix interface to Speak Freely, also developed
- by Mark Hamby.
-
- Sfspeaker showed connect and idle messages even if the "-v" option
- was not present. Fixed.
-
- Some of the cases in mike.c where a user tried to specify more than
- one of the compression modes -F, -LPC, and -T didn't exit after
- printing the error message. This resulted in the program trying to
- actually use more than one of these modes at once, which could
- heroically mess things up. Fixed.
-
- Added a gimmick to make it easier to reply to a host that's just
- connected to your machine, avoiding all the fumble-fingered typing or
- furious cutting and pasting. If you specify the
-
- -a"filename[ command ...]"
-
- option to sfspeaker, every time a new host connects, it will write
- an executable shell script that invokes sfmike to reply to the
- just-connected host. If no command is given, "sfmike -t $* hostname"
- is used, the $* allowing the user to pass options from the call on
- the reply script to sfmike. A custom command can be specified following
- the filename, separated by a space (be sure to quote the string in
- this case).
-
- 21 November 1995
-
- Discovered bad htonl() logic in loop-back code in sfspeaker. The
- length passed to sendto() had already been byte swapped. Fixed.
-
- 24 November 1995
-
- Made GSM (-t) compression the default in mike.c. Far, far, too many
- people are choosing improper compression modes, so I've made GSM the
- default for both the Unix and Windows versions. The mutually
- exclusive compression modes (ADPCM, LPC, and GSM) now simply cancel
- a previously selected mode radio-button style rather than give an
- error message. This preserves compatibility with earlier versions
- which allowed "sfmike -f", for example, without requiring an -n
- switch to turn off GSM.
-
- Converted speaker.c from alarm() to setitimer(), allowing timer
- resolution as fine as permitted by the system clock, with
- specification in microseconds. A wrapper called ularm() which accepts
- an argument in microseconds hides the ugliness of setitimer(). This
- will allow the rapid-fire time-based event generation needed to
- download face files from a remote server. This, of course, required
- little fixes all over the place.
-
- Discovered that going from idle to audio output active state in
- speaker.c didn't speed up the timeout interval to the active rate
- until the next timeout occurred. Fixed to speed up the timer at the
- moment audio output is opened.
-
- Renamed netfone.h to speakfree.h, eliminating the last vestige of the
- program's original identity.
-
- 26 November 1995
-
- Fixed a format in lwld.c that caused an incorrect error message
- when the -m message file couldn't be opened.
-
- Integrated the "show your face" code to permit users to see each
- other's pictures. A user can make a face image available by creating
- a 256 colour Microsoft .BMP format file and providing its pathname to
- sfspeaker on a SPEAKFREE_FACE environment variable. When sound is
- received from a new host, sfspeaker sends a request for a face image
- to it. If an image is available, is is transferred in packets at a
- rate configured by FaceFetchInterval in speakfree.h (in microseconds),
- and when complete, displayed using "xv" (which must be installed and
- accessible from the user's PATH). Actually, as long as the two
- communicating systems are Unix, any image format displayable by xv can
- be used, but since the Windows version only knows how to display .BMP
- files, even Unix users should restrict themselves to that format. (I
- may add code to enforce this in the future.)
-
- The somewhat radical changes in timeout logic required to support
- transmission of the face image in the background ran afoul of the
- sneaky way we were keeping timed out connections around to avoid
- forgetting their PGP session keys. Now a con_timeout value of -1
- indicates a ghost of a former connection, not (hosttimeout + 1), which
- can't be guaranteed with variable timer resolution. I changed the
- "Tick..." message generated when the -d option is set to show the
- current timer interval.
-
- Forking processes to view face images with xv was incrementing
- reference counts of resources inherited by the child process. On
- Sun, this locked up the exclusive use /dev/audio file until all the
- viewer processes terminated. I added code to release all resources
- inherited from the parent as soon as the child process receives
- control. Audio output, if open, is unconditionally closed before
- the fork() since we don't know the nature of the resource(s) it may
- bequeath to the child process. It will simply be reacquired when the
- next packet arrives.
-
- 28 November 1995
-
- Eliminated an unreferenced variable in the HDX_DEBUG code in
- speaker.c.
-
- Changed speaker.c -d option output to show the hostname from the
- connection (obtained with gethostbyname) rather than the often
- truncated and untrustworthy hostname in the sound buffer. If the
- hostname could not be obtained, the IP address is shown.
-
- To aid in diagnosing the problems of users who connect with
- inappropriate compression modes, I added a status message to the
- -v option output which identifies the type of compression currently
- being used by a connected host. The message is reissued every time
- the compression mode changes.
-
- Changed the logic of the "show your face" code to make it fully
- downward compatible with earlier releases. If SPEAKFREE_FACE is
- defined and points to a valid file, mike.c now includes a new
- fFaceOffer bit in every sound packet it sends. speaker.c only
- requests a face from the remote host if that host's packet includes
- the fFaceOffer bit. Since prior releases won't ever set that bit,
- there's no need to worry about them getting befuddled by receiving
- face requests they don't know how to process.
-
- 30 November 1995
-
- Integrated a fix from Hans Werner Strube which corrects the problem
- sending sound files on Solaris. Due to confusion resulting from the
- change-over from the BSD ftime() function which returns time as
- seconds and milliseconds to the System V gettimeofday() which returns
- seconds and microseconds, the delays computed to wait for the
- transmission of sound buffers were 1000 times too long, resulting in a
- long pause between each packet. Fixed.
-
- Increased the default host timeout from 1 to 3 minutes. Connections
- would frequently time out during long rants by the local user,
- requiring retransmission of the face file. This should ameliorate
- the problem for the time being, pending a longer-term fix based
- on RTP BYE packet handshaking.
-
- 1 December 1995
-
- Integrated a Solaris fix from Hans Werner Strube into mike.c and
- soundbyte.c which sets the audio input buffer to the actual packet
- size currently in use. This reduces the delay compared to the
- previous fixed packet size of 4000 samples. The actual buffer size
- may be rounded down to the nearest multiple of 16 on machines which
- use the DBRI device.
-
- Feature release 5.6.
-
- 2 December 1995
-
- Added a fix for FreeBSD from Andrey A. Chernov to add a required
- library to the FreeBSD link command. His other fix, to comment out
- the compiler-busting warning in RTPOUT.C since GCC requires correct
- syntax even in #ifdef disabled code was already in 5.6, thanks to GCC
- users on Solaris who encountered the same problem.
-
- 4 December 1995
-
- Hans Werner Strube supplied another Solaris / System V fix required
- for the viewerterm() function in speaker.c. The wait3() function
- present in BSD and SGI IRIX is supplanted by waitpid() in System V. As
- integrated, waitpid() is currently used only on Solaris. When I get
- time to do more testing, I may change the code to use it
- unconditionally, as even SunOS 4.1.1 seems to implement it.
-
- 5 December 1995
-
- Our clever decision to not initialise the socket until after
- processing the command line options in speaker.c (so that -u works
- even if another copy of sfspeaker is running) ran afoul of the need
- for the -M option (possibly several -M options) to have the socket
- initialised in order to add multicast group memberships. I moved the
- socket initialisation back to before the option processing loop.
- (Reported by Robert Kaempf).
-
- Added a first-pass option processing loop before the socket is
- initialised to restore the ability to use -u when another copy of
- sfspeaker is running and, more importantly, allow the -p option to
- change the port number before the socket is bound.
-
- 8 December 1995
-
- Andrey A. Chernov discovered that lwl.c and lwld.c still contained
- numerous assumptions about both byte order and the layout of bit
- fields (used in the header of the RTP- compatible packets those
- programs exchange). I installed the bit-twiddling version of the
- packet processing from the Windows version, leaving in the original
- code, disabled with #ifdef RationalWorld, since it documents what
- we're trying to accomplish a lot more clearly. The fixed code works
- fine on big-endian machines, but I haven't been able to test it on a
- little-endian myself, so it's probable I may have missed one or more
- additional fixes that may be required.
-
- Given the generally ratty state of sflwl (runs for a week without
- a hitch, then crashes 3 times in one day for no apparent reason),
- I added a bunch of new debug output when the -v option is selected
- including logging of all requests to the server. Maybe this will
- provide some clues as to what's going on.
-
- 9 December 1995
-
- Integrated fixes to the Makefile and soundbyte.c which enable the
- program to build and run on Linux.
-
- 19 December 1995
-
- Well, the earlier fixes to lwl.c and lwld.c improved (or at least
- changed) the results of trying to run sflwl on FreeBSD, but it still
- doesn't work right. Still flying blind, I took another close look at
- lwl.c and lwld.c and found two places in each where, under certain
- circumstances, a compiler treating "char" as signed might lead to
- trouble. I added defensive ANDs with 0xFF in both cases. We'll see
- if that does it.
-
- Found one more little-endian problem in lwl.c--this time it was a
- reference to a bit field in the RTP packet which caused sflwl to
- mis-count the number of items returned from sflwld. Fixed.
-
- While sflwld detected packet overflow and flagged it to the
- requestor, it didn't actually stop filling the packet. Fixed.
-
- Including sys/wait.h pulled in signal.h before _BSD_SIGNALS was
- defined on the SGI, leading to naughty System V-like behaviour
- complete with sflwld crashing with "Alarm clock" since it failed
- to re-enable SIGALRM in release(). For good measure (and to
- preempt other System V problems), I both defined _BSD_SIGNALS at the
- top of the includes and included a re-enable of SIGALRM in release().
-
- Distinguished the new debug output added yesterday from the regular
- sysadmin-level logging by enabling the former by the "-vv" option
- (very verbose) and the latter by "-v". Detailed output (-vv)
- always enables the regular verbose messages.
-
- Integrated the first-cut Hewlett-Packard audio driver code submitted
- by Marc Kilian. Marc notes that this code has not been extensively
- tested. It's up to you, HP workstation users, to wring this out and
- bring HP into the list of fully-supported platforms. You can enable
- debug output by uncommenting the #define HP_DEBUG at the top of
- hp_audio.c.
-
- 20 December 1995
-
- Fixed a few more byte-order and bitfield problems, this time in
- rtpout.c.
-
- Added some additional information to the "very verbose" trace from
- sflwld when -vv is specified, including the SDES of any SDES or
- BYE packet and the 4 letter code of APP messages.
-
- 21 December 1995
-
- Oops--missed a FreeBSD fix in the Makefile. It's in there now.
-
- As suggested by John Deters, I added an explicit "+armor=off"
- specification to the command lines used to invoke PGP in mike.c and
- speaker.c. Our use of PGP to exchange a random session key requires
- PGP to produce a binary output file, not an ASCII armoured one, as it
- usually does unless the "a" option is specified. The user can,
- however, make ASCII armour the default by setting the "Armor=on"
- option in the config.txt file; doing so caused Speak Freely's use of
- PGP to fail. Configuring armor off on the command line overrides the
- config.txt specification and prevents this problem.
-
- 27 December 1995
-
- Edward Olszewski reported that the "cc" compiler on HPUX 9.05 (HP 9000
- 735/125) (like SunOS cc) couldn't handle the "const" modifier in the
- argument declarations in md5/md5.c. To avoid an ever-growing
- exception list, I just removed the "const". It won't make any
- difference in operation.
-
- In addition, random() (referenced in lpc/lpc.c) was undefined in the
- link. I modified lpc.c to enable the emulation of random() with
- lrand48 for HEWLETT_PACKARD as well as Solaris.
-
- 31 December 1995
-
- On some systems (Silicon Graphics, for instance) if the sfspeaker
- timer happens to expire while we're waiting for the fread() from
- the PGP session key decode pipe to complete (this usually happens
- when it takes the user longer to enter the secret key pass phrase
- than the interval to the next timer tick), the fread() can return
- with zero bytes read and errno set to EINTR (Interrupted system call).
- I modified to the logic that reads from the PGP decode pipe in
- speaker.c to detect this condition and re-issue the fread() until
- it either succeeds or fails with a status other than EINTR.
-
- 4 January 1996
-
- Finished first cut of sfecho (echo.c), a remote echo server intended
- to allow users, even those with half-duplex audio hardware, to perform
- remote "sound checks" of various compression and encryption modes
- without the need for an individual on the other end to evaluate sound
- quality. The server simply time stamps sound packets as they arrive,
- then sends them back to the originating address ten seconds later.
- No audio I/O is performed, so the echo server can be run on a machine
- without audio capability.
-
- 5 January 1996
-
- The microsecond-resolution packet timing in echo.c will overflow a
- long and go negative in less than an hour. The way the code was
- structured, this actually didn't cause any trouble unless a packet
- happened to be queued right at the time the wrap-around caused the
- sign to change. I modified the code to use a double for the packet
- time to make sure there's no wrap-around.
-
- I changed the logic in makeSessionKey() in echo.c to use only MD5, not
- idearand(), to construct the RTP SDES sent to the LWL server. Since
- there's no other reason to include IDEA in sfecho, eliminating this
- one reference gets rid of the whole IDEA patent disclaimer on the
- sfecho.1 manual page.
-
- The logic in echo.c is perfectly capable of supporting a face image
- file for the echo server, for which I was originally planning to use
- an image of a statue of the Greek goddess Echo. Well, not only
- haven't I been able to locate such an image, on reflection (hee, hee)
- I've decided that giving the echo server a face is a bad idea,
- especially for a widely-used public server running on a line with
- limited bandwidth. It would be very easy for the volume of face data
- sent to all accessors to dwarf the sound packet bandwidth, inducing
- pauses and lost data that gave echo server users a false impression of
- the actual response. Not being one to ever actually delete working
- code, I turned off the echo face capability with #ifdefs on ECHO_FACE
- so it can be restored if future events prove that to be wise.
-
- 8 January 1996
-
- The echo server program, echo.c, inherited logic from speaker.c to
- disable publication of its identity on the SPEAKFREE_LWL_TELL server
- if a connection is refused. This is intended to keep machines which
- once ran an LWL server but don't any more from being repeatedly
- bombarded with LWL packets. Unfortunately, this means that if an LWL
- server is momentarily out of service, the echo server will disappear
- from the LWL directory until it restarts the next time; this is bad.
- So, I removed the disabling due to connection refused in echo.c,
- trusting the administrator of an echo server to be responsible enough
- to respond to the repeated warning messages for refused connections
- when an LWL server is genuinely rather than transiently down.
-
- In an attempt to fix the sporadic "broken pipe" crashes of the sflwld
- server (every three or four days on the SGI, typically), I'm
- proceeding on the hypothesis that this happens when a user submits a
- request and then shuts down (or crashes) before we write the reply
- back to the socket. (I have not, however, even with a deliberately
- broken version of sflwl, been able to make this happen.) Anyway, I
- added a SIGPIPE signal catcher which ignores the signal (at the
- moment, printing a message when this happens). This should allow the
- send() to return and the connection to be closed normally. There's
- nothing else we can do about it anyway.
-
- 10 January 1996
-
- The critical section locking code in echo.c wasn't entirely
- bulletproof against a host timeout occurring while processing a sound
- packet from that host, or while scanning the connection chain and/or
- making an entry for a new host. I revised the logic to include all
- references to the connection chain as well as the queued packet list
- within the critical section that blocks the timer interrupt. In
- addition, I revised the detection of host timeouts and LWL
- retransmissions in release() to be based on absolute time rather than
- a countdown timeout. This permits release() to be called at any time
- whatsoever without worrying about whether the proper timeout interval
- has elapsed and, hence, to be called whenever the critical section
- lock is released if the timeout has expired while the lock was set.
- This timeout logic is a lot cleaner and deserves to be integrated into
- speaker.c once it's proven in the more demanding environment (due to
- rapid-fire packet timing interrupts) of echo.c.
-
- 21 January 1996
-
- Added a hexadecimal dump (-x) option to sfspeaker if it's
- compiled with HEXDUMP defined. One more little tool to help
- debug RTP and VAT support.
-
- Found a place in speaker.c's LPC decompression function
- lpcdecomp() where an ntohl() was needed in extracting the
- decompressed length of the message.
-
- 28 January 1996
-
- Staked another bloodsucking byte-order dependency in lpccomp() in
- mike.c.
-
- Added a reality-check in playbuffer() in speaker.c which discards
- packets with a buffer.buffer_len field longer than the actual packet
- read from the socket. This prevents embarrassing blasts of noise or
- worse if we receive a garbage packet due to improper protocol
- recognition or an incorrect encryption key on an RTP or VAT
- connection.
-
- Playbuffer() in speaker.c made a redundant test on showhosts. Fixed.
-
- Added monitoring of the control port (data port + 1) to speaker.c to
- recognise VAT and RTP connections. A new con_protocol field in the
- connection structure indicates the protocol of the connection. The
- reply command will now contain the sfmike appropriate option to send
- in the protocol we're receiving.
-
- 29 January 1996
-
- Integrated a decode-only version of Dave Hawkes' VOX compression mode.
- I'm not close to being able to make the compressor available, but at
- least this this code in place, Unix users can receive packets sent by
- the Windows version with this compression mode. All the encoding
- logic is present in the module VOX.C, but disabled pending
- integration.
-
- Made innumerable fixes in the VAT and RTP support code and associated
- packet translators. For the moment, everything is pretty much working
- except for LPC; neither NEVOT nor VAT seem to be able to talk to one
- another in LPC mode so I'm not sure the problem is of my making. GSM
- and all the other common modes work fine. It's a little odd that VAT
- ID and RTP SDES packets are sent by sfmike as well as sfspeaker; to be
- marked as a participant in a conference you have to run sfmike with
- its ID (though you do not have to actually transmit anything). I may
- change this, but for the moment getting this logic into the Windows
- version (which does not share our schizophrenic view of connections)
- is a much higher priority.
-
- 31 January 1996
-
- The "plumber()" code in lwld.c that catches SIGPIPE signals when a
- remote user disconnects while we're tring to send the reply to a query
- seems to be working well. So, to tempt fate, I disabled the log
- message when we recover from a SIGPIPE.
-
- After struggling 2 days trying to figure out why I could receive
- LPC-encoded sound just fine from VAT, and send it to myself with no
- trouble in LPC format, but was unable to send LPC sound to VAT, I
- decided to download a newer VAT. I got the 4.0a2 alpha release, and
- no trouble with LPC in either direction. I guess it just didn't work
- in earlier versions of VAT.
-
- To avoid confusing those familiar with VAT, mike.c now parses
- destinations in any of the following formats:
-
- hostname
- hostname:port
- hostname/port
- hostname:port/ttl
- hostname/port/ttl
-
- Integrated DES encryption code into the VAT and RTP output handlers
- in mike.c. Like everything else in the funhouse of VAT and RTP,
- results are mixed. Clearly VAT and I agree on key generation, since
- the sound I send is played OK, but with ticking between each
- packet in GSM mode, indicating VAT doesn't handle the padding of
- packets to 8 bytes correctly. Well, thank goodness RTP introduced
- the "P" flag! But NEVOT doesn't seem to recognise any DES encrypted
- inbound packets in RTP mode! So, let's try the new VAT--uhhhh, it
- appears they've totally pulled DES support from it due to "export
- control" restrictions. Gosh this is fun.
-
- 1 February 1996
-
- After several more hours of psychoanalysis of the RTP spec and
- examination of the VAT and RTP source code, DES encryption of RTP
- packets works in both directions when I test with NeVoT 3.32. I can't
- test RTP encryption with VAT 4.0.a2 alpha since they've disabled
- encryption due to ITAR fears. At present, I assume that if RTP
- encryption is enabled, both control and data packets will be
- encrypted, and this is how NeVoT behaves. RTP allows RTCP control
- channel packets to be either encrypted or in the clear--you're
- supposed to detect a clear packet by verifying that it meets
- rather easy-to-spoof consistency conditions. This gives me the
- willies; I'll defer such "heuristics" until things settle out more in
- RTP land.
-
- With even more hacking, I can now talk to NeVoT in RTP mode both
- directions with DES encryption, more or less. The less is that for
- some reason ADPCM picks up noise and, of course, LPC doesn't work
- right (but it never did, even without DES). VAT doesn't pad packets
- when encrypting, and I haven't guess the golden rule that governs how
- the packet is initialised when it is encrypted. (Hint: it isn't
- zeroed--I tried that.)
-
- Integrated a fix from Paul Eggert for Solaris 2.5 in mike.c. In
- Solaris 2.5 gettimeofday() is required to have two arguments--you have
- to pass an explicit NULL if you don't want the time zone information.
- Both references that failed to supply the NULL now do.
-
- Removed the terminal protocol dependent modules from libdes.a to avoid
- nugatory incompatibilities in ports.
-
- 2 February 1996
-
- Modified rtp_make_sdes() and rtp_make_bye() in rtpacket.c to
- optionally create a composite RTCP packet with a void Receiver Report
- at the start if called with a new "strict" argument TRUE. The RTP
- spec requires an RTCP packet to always begin with a (possibly void) SR
- or RR. Why make it optional? I had missed this little twist when I
- implemented lwld.c, and though I'll fix lwld.c to accept packets in
- this format, existing servers won't understand them until they install
- the updated version. So, we'll go on sending the old format to LWL
- servers for a while.
-
- "Just in case", I deleted the private items used only by the LWL
- server from the SDES packet if strict is set. They're perfectly
- legal but, you know....
-
- Added unconditional padding of the whole packet to a multiple of 8
- bytes in rtp_make_sdes() and rtp_make_bye(). Later on, we may want to
- encrypt these packets, and it's a lot easier to pad them at generation
- time when we understand the composite nature of the packets than at
- encryption time, when we'd prefer to treat them as a black box.
- Padding is done only for strict calls, for the same reasons given
- above.
-
- If strict is set rtp_make_sdes() now deletes the leading asterisk (if
- present) from the RTCP_SDES_CNAME and RTCP_SDES_EMAIL which servers
- only to inform an LWL server that the user permits exact matches only
- of his E-mail address and doesn't wish to be listed in the HTML
- directory. The asterisks could confuse an RTP client, so we don't
- send 'em.
-
- Modified lwld.c so it understands packets which comply with the RTP
- requirement that all RTCP packets begin with an SR or RR packet. In
- the future, once all the servers are running this version, we'll be
- able to use the same SDES packet for the LWL server and to send to RTP
- connections. I also verified that lwld.c works even if the packet it
- receives contains padding. Note that only the first eligible RTCP
- message in a packet is processed--If you stack multiple requests in
- one packet, only the first will be processed.
-
- Fixed a raft of byte order and bit field order independence problems
- in rtpacket.c; isrtp() (this had never had the RationalWorld treatment
- applied to it, since it didn't make sense to uglify it before it was
- even working). I also added logic to skip a header extension, if
- present. Since none of the tools I have to test with ever includes a
- header extension, I can't be absolutely sure I've got this right.
-
- Added a new isValidRTCPpacket() function to rtpacket.c, based on the
- validation technique suggested in the RTP spec. This is now called
- in speaker.c for two purposes. First, the protocol of a connection is
- set to RTP only when a valid RTCP message is received rather than for
- any control message with a version of 2. This makes it much less
- likely the protocol will get set to RTP accidentally by an encrypted
- VAT control message that we don't have the key to properly decode.
- Second, if a DES key is supplied and we receive a message on the
- control channel which passes all the tests for RTCP validity as
- received, we don't decrypt it. This allows RTP programs to either
- send control messages in the clear or encrypt them; both behaviours
- are permitted by the RTP spec.
-
- Fixed mike.c to encrypt RTCP BYE and VAT DONE packets when encryption
- is enabled. NeVoT accepts the encrypted packets with no difficulty.
-
- Moved the generation of VAT DONE packets from in-line code in mike.c
- to a new makevatdone() function in vatpkt.c both for purity of essence
- and to make it easier to move the code to Windows.
-
- Fixed an oddity that caused VAT 4 not to recognise a DONE packet in
- the form that was sent by VAT 3. I copied the VAT 3 packet, but
- apparently it had garbage bits in the flags field that VAT 4 didn't
- like. I zeroed the flags field and all was well.
-
- Modified makeVATid() in vatpkt.c to take the E-mail address from the
- SPEAKFREE_ID variable if no SPEAKFREE_CNAME is specified. If neither
- is present, an ID is made up from the password file information as
- before.
-
- Fixed makeVATid() in vatpkt.c to delete leading asterisks on the
- SPEAKFREE_CNAME and SPEAKFREE_ID E-mail addresses just like rtpacket.c
- does.
-
- Added logic in mike.c and rtpacket.c to set the marker (M) bit in the
- RTP packet header for the first packet of a "talk spurt". This
- conforms to the behaviour of VAT 4 in RTP mode.
-
- Added documentation of the -rtp and -vat options to the sfmike.1
- manual page.
-
- Implemented a major revision of the "squelch" (a.k.a. VOX) code in
- mike.c. While still nothing close to as nifty as Dave Hawkes' VOX
- code in the Windows version, this is a great improvement over the
- pathetic attempt at VOX that preceded it. This version tests the
- maximum energy in a packet in the linear domain, not the logarithmic
- (which, notwithstanding psychoacoustics, our users understand much
- more clearly), and allows you to specify as a second comma-separated
- argument to the -s option, the time in milliseconds transmission
- should continue before muting transmission. In addition, the push to
- talk console display now shows "Quiet:" when Talk mode is enabled and
- output is squelched.
-
- 3 February 1996
-
- Added the capability to echo VAT and RTP packets to sfecho. This
- involved having echo.c monitor both control and data sockets as
- sfspeaker does, and return packets received to the same port from
- which they originated. The (soon to be remedied) potential ambiguity
- between Speak Freely and VAT packets means uncompressed VAT packets
- can be mistaken for Speak Freely sound buffers. We only consider a
- packet as VAT if we've previously received a message on the control
- port from this connection, and if it is in an audio format we know VAT
- to use. Note that mistaking the format of a packet only affects the
- log messages generated when the -v option is on; since packets are
- bodily returned to the originator without examining their content, the
- actual echo process does not require recognition of packet format,
-
- Handling VAT and RTP packets without peeking inside made it impossible
- to maintain the (already disabled for other good reasons) echo
- server's ability to show a face file. I ripped out all the code for
- that potential but ill-considered feature.
-
- To avoid potential confusion between Speak Freely sound buffers and
- VAT packets, I modified packet generation code everywhere to always
- set the new fProtocol (0x40000000) bit in the compression field of
- every sound buffer we send. This won't interfere with older versions
- of Speak Freely, but will keep VAT compatible programs from attempting
- to interpret Speak Freely packets as VAT format. (The protocol flag
- turns into a VAT/RTP P value of 1, which was used by the now-obsolete
- first draft of RTP. We should never see it sent by a current program.)
- Once all versions of Speak Freely are sending the fProtocol bit, we'll
- be able to increase our own level of discrimination between VAT and
- Speak Freely packets.
-
- Implemented another major turn of the screw to avoid spoofing by
- improperly decrypted packets. RTP and VAT sound packets are now
- accepted only if the session ID (conference ID for VAT, SSRC for
- RTP) received in the last control message for this protocol agrees
- with that contained in the sound packet. This makes it vastly less
- likely we'll be fooled again by a Speak Freely sound buffer after a
- protocol change or a message we can't decrypt.
-
- To avoid incorrectly decrypted VAT and RTP packets from being
- interpreted as Speak Freely sound buffers, I added a check in
- speaker.c that verifies the length in the buffer.buffer_len field
- against the actual length of the packet read from the socket (this
- must take into account the padding to a multiple of 8 bytes which
- occurs if DES, IDEA, or PGP encryption is indicated by the flags in
- the header). This is a pretty good test for validity, since the odds
- of 4 encrypted bytes precisely equalling the received packet length
- are very slim. If a bogus packet is detected, it is ignored and the
- protocol for the connection reset to PROTOCOL_UNKNOWN, which allows us
- to restart protocol recognition. This, in turn, permits us to
- identify unencrypted Speak Freely sound buffers which may arrive,
- unless we're reset to VAT or RTP modes by the subsequent arrival of a
- packet on the control port.
-
- 4 February 1996
-
- The code which inserts a 4 random bytes before an RTCP message that's
- being encrypted in sendrtpctrl() in mike.c was broken, and didn't test
- whether the message was VAT (which doesn't have the random prefix) or
- RTP. Fixed.
-
- In the process of testing the above fix, I discovered that the
- generation of SDES and BYE packets in rtpacket.c must actually pad
- packets to an *odd* multiple of 4 bytes. Why? Because the length
- of the block to be encrypted needs to be a multiple of 8 bytes, and
- that includes the 4 byte random prefix. So the original packet needs
- to be an odd multiple of 4.
-
- Just a note in passing: the DES encryption used with VAT and RTP is
- standard DES including the initial and final permutations which Speak
- Freely dispenses with in its own modified DES. This slows down the
- encryption and decryption process quite a bit (which is precisely what
- it's intended to do, of course), but we have no choice since that's
- what the RTP spec and VAT software require.
-
- Padding of RTP sound packets when encrypting with DES was wrong.
- Fixed.
-
- Shuffling the pad byte to the end of the frame for LPC compressed
- sound in rtpout() (rtpacket.c) wasn't quite right. Fixed. While I
- was at it, I modified isrtp() to do the inverse byte shuffle rather
- than call lpc_analyze() to decompress the sound. This also fixes
- sfspeaker's identifying LPC compressed sound in an RTP packet as
- "uncompressed".
-
- Replaced the hokey random prefix generation for DES encrypted RTCP
- packets used by sendrtpctrl() in mike.c with a proper set of random
- bytes derived from the same MD5 source used for the SSRC, timestamp,
- and sequence number fields.
-
- 6.0-Alpha 1 prerelease.
-
- 5 February 1996
-
- Installed fixes for three problems reported by Jay Novello when
- building on Solaris 2.4 with gcc. Two places in rtpacket.c I stored
- an unsigned value > 127 into a char. Gcc natters at this, so I
- changed the variable in question into an unsigned char. Let's see
- what natters this sets off elsewhere (on SunOS and SGI it compiles
- cleanly). Second, in soundbyte.c, the same apparent incompatibility
- between stdlib.h and math.h that surfaced on SGI seems to afflict
- Solaris/gcc as well. I commented out the #include of math.h and
- verified that doing so didn't break anything on SunOS.
-
- Added receive-only support for RTP PCMA (payload type 8) packets. The
- A-law samples are translated into mu-law samples one for one. I
- haven't been able to test this since I haven't yet found a program
- which sends PCMA. There's no reason to support sending in this format,
- as minimum compliance with RFC 1890 requires support of PCMU (payload
- type 0), and there is no RTP channel capable of transmitting PCMA
- which cannot equally well transmit PCMU. Adding PCMA inbound support
- checks off another RTP payload type which we may increasingly
- encounter as ISDN telephony begins to interact with the Internet.
-
- 9 February 1996
-
- The code in speaker.c that initialises the con_session field
- in the connection structure thought it was 8 bytes instead of
- 4. Fixed.
-
- System V's ever-so-clever trick of blowing off pending system calls
- with an EINTR status when even a timer signal occurs caused horrors in
- in mike.c's sendfile() of which even Billy Boy would have been proud.
- The read (Pause mode) or poll (Talk mode) of standard input to see if
- we should toggle transmit can return not only when a character is
- available, but also when the timer pops. Testing for -1 status
- doesn't work on BSD because there you get a -1 with a WOULDBLOCK errno
- when no character is available. On System V, that case returns 0
- characters read and no error. So, we have to test for a return status
- of -1 and errno == EINTR to decide we should retry the read. A
- similar condition in the initial read to transition into Talk mode
- required wrapping that read in a loop which is broken only on
- non-EINTR conditions. This fixes the "jumps into Talk mode even when
- I didn't press a key" and "sends a blip of sound every 7 seconds even
- when I'm in Quiet" bugs.
-
- 10 February 1996
-
- Ripped out some obsolete code in isvat.c that tried to discriminate
- VAT packets from Speak Freely packets by checking the consistency of
- the Speak Freely header. With the determination of the protocol based
- on control channel messages and verification of the session ID in the
- packet, this is no longer necessary.
-
- Integrated some fixes to isvat.c from the Windows version which may
- avoid warnings on Unix compilers pickier than those I use.
-
- Isvat() and isrtp() used to look at information in the connection
- structure when processing the packet, but no longer do. I removed the
- unused connection argument, which makes the functions more portable
- between the Unix and Windows versions.
-
- 12 February 1996
-
- I decided to tackle the problems of the LPC decoder head-on. First of
- all, I started with the version of LPC.C from the latest VAT source;
- this version has been modified so the decoder state is kept in a
- separate structure so multiple simultaneous streams don't confuse the
- decoder. I further modified it to dynamically allocate the large
- static and automatic arrays used in the coder and decoder; new
- functions lpc_start() and lpc_end() allocate and release the work
- buffer, respectively. The main rationale for this is that it's
- necessary to keep these arrays out of the 64K data segment on 16 bit
- Windows, and doing it here as well minimises differences in the code
- and costs nothing.
-
- To try to nail down the divide by zero and DOMAIN ERROR in sqrt()
- problems, I ran various tests using standard audio test files. First
- I discovered that absolute silence (rarely encountered with a real
- microphone but common in edited sound files) could cause durbin() in
- lpc.c to divide by zero. I added code to detect the incipient divide
- by zero and return a zero gain value. This fixes the problem where
- true silence was rendered as hiss. I also discovered that in certain
- circumstances (probably due to roundoff of floats) the gain can go
- negative by a tiny epsilon, but all it takes to make sqrt() report a
- DOMAIN ERROR. I added a test for negative gain and zero the value
- before the square root is taken. Both of these changes are enabled
- only if SILENCEFIX is defined, which it is by default.
-
- Given the horrors which LPC encoding results in when driven into
- clipping, I added a new definition, GAIN_ADJUST, set to 0.9 by
- default, which is used to scale the linearised samples before
- processing. Given that many users set their mike very hot, counting
- on the other coders not to mind an occasional clip, this has the
- effect of reducing the gain when encoding in LPC and avoids some of
- the worst clipping. Given that sound perception is logarithmic, I
- don't think the difference will be very perceptible.
-
- 13 February 1996
-
- ADPCM packets sent by sfmike in RTP protocol sounded ratty due to an
- error in the calculation of RTP packet length in rtpacket.c's rtpout()
- function which accidentally truncated the last two samples in the
- packet. Fixed.
-
- 14 February 1996
-
- Added an RFC 1890 string-to-key mapping for DES encryption of RTP
- packets. The code was borrowed from a routine in NeVoT's netutil
- directory. Both mike.c and speaker.c call the new routine in deskey.c
- to generate RTP encryption keys. This new code recognises RFC 1890
- encryption algorithm specifications, but only DES-CBC is accepted; any
- other encryption mode exits with an error message.
-
- To avoid protocol spoofing, I added code to reset the connection's
- receive protocol to PROTOCOL_UNKNOWN when an RTP or VAT BYE/DONE
- message is received and when any connection times out. If the -v
- option is set, RTP and VAT bye message are now logged with a
- "connection closed" message.
-
- My code that zeroes the pad at the end of an RTP or VAT encrypted
- buffer was a little too clever--it cleared the length of the pad as
- well as the pad bytes! Fixed in speaker.c.
-
- Since VAT and RTP have different conventions for converting key
- strings to DES keys, I had to separate the VAT and RTP keys into
- separate buffers. This causes no trouble in mike.c, but it really
- bollixes up automatic protocol sensing in speaker.c. I added logic
- which uses the correct key as long as the protocol is known. If the
- protocol is unknown or we've received an indecipherable packet, we try
- the RTP and VAT keys on alternate control channel messages until we
- successfully crack a packet. Since any protocol error resets the
- protocol to unknown, this should us to home in on the protocol
- relatively quickly.
-
- Added a general purpose RTCP SDES parser, parseSDES(), to rtpacket.c
- and placed the definitions for the structures it uses in the new file
- rtpacket.h.
-
- If the "-v" option is specified, sfspeaker now shows the user name and
- E-mail address (if available) from the identity packets received on
- the control port. The user information is updated every time it
- changes. The code does not currently handle packets with multiple
- sources--only the first source in the packet is returned.
-
- VAT prefers the user's long name from the password file for its
- identity packets. I modified makeVATid() in vatpkt.c to behave the
- same way.
-
- I increased the packet lengths for RTP and VAT protocols to the
- largest sizes within both the RTP/VAT experience base and the
- the 512 byte Windows packet constraint.
-
- Integrated a couple of byte order fixes discovered in the Windows
- version into isrtp() (rtpacket.c) and isvat() (vatpkt.c).
-
- 15 February 1996
-
- Added another little tweak to automatic protocol recognition of
- encrypted control messages in speaker.c which should speed the
- transition on a Speak Freely to RTP or VAT protocol change.
-
- 16 February 1996
-
- Added code in mike.c and speaker.c and modified functions
- isValidRTCPpacket(), isRTCPByepacket(), and parseSDES() in rtpacket.c
- to support Speak Freely session control messages. The messages sent
- and received are identical to RTP SDES packets, except the protocol is
- set to 1 to indicate Speak Freely. Speak Freely never encrypts its
- session control messages, so the existing check for an unencrypted
- control messages takes care of this condition.
-
- Oops--forgot to enable the periodic re-send of the SDES item if
- the procotol selected is Speak Freely. Fixed.
-
- 22 February 1996
-
- 6.0-Alpha 2 prerelease.
-
- 23 February 1996
-
- Some people ran into library incompatibilities compiling files in
- libdes which aren't actually used by Speak Freely. I made a
- Makefile.sf which builds only the files we need, and tweaked the
- libdes/des.h file to not define crypt(), which conflicted with the
- definition in unistd.h.
-
- 25 February 1996
-
- Added logic to echo.c to recognise RTCP BYE and VAT DONE packets and
- mark the connection closed without retransmitting the packet to the
- other end. This fixes the problem where a user closes a connection to
- the echo server, only to have it pop back open when his own BYE packet
- comes back. (Yes, it seems dumb to open a connection upon receipt of
- a BYE packet, but it is very easy for an encrypted RTP SDES message to
- look like a VAT DONE, so we have to allow an apparent VAT DONE to open
- a connection. Sigh.) Note that this will not work if the user is
- sending encrypted RTP or VAT packets to the echo server. Receipt of a
- BYE causes the host to go idle on the next timer tick without waiting
- for the usual inactivity timeout.
-
- Lazarus echo connections could also result if packets remained in the
- retransmission queue for a given host at the time we receive a BYE
- message from it. I added code in echo.c to discard any packets queued
- to a host at the time it disconnects.
-
- Modified debug output from sfecho to use a slash between the IP
- address and port number, as is becoming the usual convention.
-
- Finished "sfvod", the "voice on demand" server. Actually, this is
- just a hack in Perl which monitors a port pair and, at each new
- connection, forks a process which sends one or more sound files or
- live audio to the connected site with sfmike. If the site disconnects
- before the transmission is done, sfvod detects this and kills the
- sfmike process. You can write a log in NCSA HTTPD format of all
- requests processed by the server. You can run as many copies of sfvod
- as you like, each monitoring a different port, to allow users to
- retrieve different audio available on a host.
-
- 6.0-Alpha 3 prerelease.
-
- 26 February 1996
-
- Once again, it's demonstrated that not even the simplest program can
- esape the wiles of BSD and System V co-consipiring to pump it full of
- arcana. Today's victime du jour is sfvod, which encountered the
- following problems on System V. First of all, its socket recv() call
- was getting nailed by System V's favourite trick, the EINTR error
- return when the timer signal arrives. Further, Jay Novello reported
- that on Solaris 2.4 he was getting an error return from the socket at
- the end of each connection with an ECHILD status. This doesn't make
- any sense according to any of the documents I have, since ECHILD isn't
- a defined return status for recv(), but I put in code to ignore that
- status as well as EINTR and silently retry the recv(). Next, the
- timer and child process reaper signal handlers were getting clobbered
- on System V because they did not re-establish the signal by
- re-assigning to the %SIG variable at the end of the interrupt service
- procedure. Did you know that the semantics of signal handling in Perl
- depend upon whether the platform you're running is BSD or System V? I
- do now.
-
- But even that was not enough. You see, on SunOS SOCK_DGRAM is defined
- as 2, while on IRIX it is 1, so the socket creation was failing since
- the value of 2 I used means SOCK_STREAM on IRIX. I added an ugly hack
- to the Makefile to create an ephemeral C program which is compiled and
- run to insert the system's definitions of AF_INET and SOCK_DGRAM at
- the head of sfvod.
-
- 27 February 1996
-
- Speak Freely failed to sense VAT protocol when connected to a CU-SeeMe
- reflector because Speak Freely required a user ID as received in a
- point to point VAT connection, whereas the reflector sends IDLIST
- (type 3) packets. I modified the protocol sensing logic in speaker.c
- to accept IDLIST packets as indicating VAT protocol.
-
- The CU-SeeMe reflector's periodic status packets were confusing
- isvat() in vatpkt.c into returning invalid sound buffers. Fixed.
-
- Added the ability to include a "conference ID" in VAT packets, but
- since nothing seems to work if you send VAT a nonzero conference ID, I
- always set it to zero at the moment.
-
- With the advent of "voice on demand", the need to be able to transmit
- pre-compressed audio has become apparent. I added a gimmick to mike.c
- which, if a sound file is specified with the extension ".gsm", assumes
- it to be the GSM compressed output of "toast" and transmits it in GSM
- packets without any additional processing. The fact that there is no
- overhead at all for these packets makes it crucial to set kOverhead
- right in mike.c. It's clear I'm going to have to put in an adaptive
- auto-set mode for this tweak.
-
- 28 February 1996
-
- All the various compression and encryption modes, combined with the
- wide range of machine performance encountered was beyond the ability
- of the simple timing loop used when transmitting sound files. I
- modified it to measure the actual time between packets, compare it to
- the correct inter-packet time based on the number of samples in the
- packet, and correct the wait time using an exponentially smoothed
- moving average with smoothing factor of 0.9. This will, in most
- cases, home in quickly on the correct delay without being upset too
- much by instantaneous changes in system load.
-
- The more accurate calculation of packet cadence times ran squarely
- into an eccentricity of usleep() on BSD--if you call usleep() before
- the previous setitimer has gone off, the nearer-term delay will apply.
- This could lead to disaster when our own timeout went off. I modified
- the private copy of usleep() in usleep.c, now renamed sf_usleep(), to
- behave reasonably, including stacking and unstacking preexisting
- SIGALRM handlers and interval timers. All platforms now call
- sf_usleep(), eliminating the different handling of this function all
- over the program.
-
- Added a nicer status message when connected to a VAT conference that
- shows who's in the conference and updates every time the members
- change. I increased the size of the "user name" field (con_uname) in
- the connection structure in speakfree.h to accommodate longer
- conference lists and protect against lists longer than the field size
- overwriting the structure.
-
- Integrated three fixes from Eugene Crosser in mike.c and soundbyte.c
- for problems experienced on Linux and with half duplex in general:
-
- 1. In mike.c line 657, if sfspeaker is not running on the local
- host, soundinit() is not executed, causing soundrab to read
- from unopened fd.
-
- 2. In mike.c line 1195 return from main() leaves the terminal in
- noecho mode.
-
- 3. In soundbyte.c line 119 set nonblocking mode on audio is not
- executed on Linux. Thus sfmike blocks in soundflush() on the
- second pause/talk toggle.
-
- 6.0-Alpha 4 prerelease.
-
- 29 February 1996
-
- When sending live audio from a Solaris system, the read() from
- /dev/audio in soundgrab() (soundbyte.c) could be blown away by the
- timer signal. Fixed to retry if it fails with EINTR.
-
- Cleaned up the #ifdefs around the sound packet timing code in mike.c
- to make the BSD_like and System V cases always mutually exclusive.
-
- Sflwl could crash if "-vv" debugging was enabled and a BYE packet was
- received out of the blue from host when no hosts were connected.
- Fixed.
-
- 1 March 1996
-
- When I integrated the little-endian fixes into vatpkt.c from the
- Windows version, I fat-fingered two instances, using ntohs() instead
- of htons(). Since these functions are, in fact, identical on every
- machine I am aware of, this worked but was unclean. Scrubbed and
- polished.
-
- 5 March 1996
-
- Feature release 6.0.
-
- 10 March 1996
-
- Revised simple (-C / 2X) compression to use the linear interpolation
- rate conversion routine from "sox". It still doesn't sound great, but
- it's better than it used to be.
-
- 11 March 1996
-
- If the user combined key file encryption with one of the 8 byte frame
- encryption methods (IDEA, PGP, or DES) and the original packet was not
- a multiple of 8 bytes, the last frame would be incorrectly decrypted.
- Speaker.c was not key-file decrypting the pad bytes at the end of the
- packet as required by the subsequent decryptions. Fixed.
-
- Integrated the NSA LPC-10 2400 baud CODEC as an option for Speak
- Freely protocol. It's kept in a new lpc10 directory, and activated
- with the "-lpc10" option on sfmike. Note that this CODEC is entirely
- unrelated to that selected by "-lpc" and cannot be used in RTP and VAT
- modes because it is not one of the forms of compression prescribed for
- those protocols. Due to the extreme (better than 25 to 1) compression
- of this protocol, per-packet overhead becomes a substantial part of
- the bandwidth sent. I added a dirty trick called "packet stuffing"
- for use with this compression mode. The no longer used 16 byte
- "sendinghost" field actually carries the last 16 bytes of the packet.
- Stuffed packets are re-shuffled upon receipt by speaker.c. For
- compatibility, stuffing is used only with the new LPC-10 compression
- mode; for the other modes the 16 byte overhead is not that significant
- an overhead.
-
- Stuffing reduces the per-packet overhead to 8 bytes, with a 78 byte
- packet carrying an original payload of 1800 uncompressed samples. The
- outbound data rate is, then, 346 bytes per second, or 2773 bits per
- second.
-
- 22 March 1996
-
- Sending nonencrypted packets to multiple hosts in Speak Freely
- protocol on a little-endian machines failed because sendpkt() in
- mike.c didn't undo the htonX() transformations of fields in the sound
- buffer before sending the packet to the next destination host.
-
- Sending nonencrypted packets to multiple hosts in Speak Freely
- protocol using LPC-10 compression failed because the "packet stuffing"
- done to reduce the number of bytes per packet in LPC-10 protocol was
- not reversed after transmitting a packet to a given host. Fixed in
- mike.c.
-
- 23 March 1996
-
- Sending packets to multiple hosts in LPC-10 robust mode sent invalid
- packets to all but the first host after the first 128 packets had
- been sent. The "unstuff" code in sendpkt() in mike.c was clearing the
- robust mode sequence number in the buffer.buffer_len field after
- unstuffing, not before as required. Fixed.
-
- 24 March 1996
-
- Integrated the compression type editing code from speaker.c into
- echo.c so the echo server -v connection log will distinguish LPC-10
- from uncompressed packets.
-
- 6.1-Alpha 1 prerelease.
-
- 28 March 1996
-
- To avoid problems with C libraries that don't define nint(), I
- incorporated the round() replacement for nint() from the CELP library
- and modified all the references to nint() in the lpc10 library to use
- L_nint(), which is #defined to round() in lpcdefs.h. This roundabout
- redefinition allows going back to an inline implementation of nint()
- if that proves important for performance reasons.
-
- 6 April 1996
-
- In order to get rid of compiler warnings on Solaris, I added a
- typedef signalFUNC to the signal function type in the #ifdef
- Solaris block in speakfree.h and modified the #define signal()
- for Solaris to cast its second argument to this type. In
- addition, I added a definition of signalFUNCreturn which casts a
- value to this type on Solaris and is void on other platforms.
- This is used in usleep.c to cast the result of signal(). This
- code may be applicable on other System V platforms, but I'm not
- going to enable it on speculation.
-
- All of the Speak Freely executables used argv[0] as the program
- name in usage, status, and error messages. When the program was
- executed with long explicit path name (as if often the case when
- daemons are started at boot time), this generated a lot of clutter
- in the log file. I added a prog_name() function which trims all
- but the final executable name from the argv[0] string and uses that
- as the program name. Sfvod.pl already contained this logic, so there
- was no need to modify it.
-
- 7 April 1996
-
- Specifying options (compression modes, for example) on sfvod to be
- passed on to sfmike didn't work since they got appended to the sound
- file name(s) instead of appearing before the -p specification of the
- destination(s). I modified the command line parser in sfvod.pl to
- distinguish sound file names from post "-" options, assemble them in
- separate strings, and emit the options before the destinations on the
- sfmike command line. I also added code to echo the command line when
- the "-d" option is set; this makes it easier to debug what's being
- passed to sfmike.
-
- Added a new "-Wport" option to sfspeaker which causes it to do nothing
- other than publish its identity on an Look Who's Listening server.
- This allows sfvod servers to identify themselves without adding all
- the complexity of direct communications to sfvod itself. When invoked
- with "-Wport", sfspeaker does not create or bind any inbound sockets.
- This allows it to coexist with other copies of sfspeaker running on
- the same machine regardless of how they were invoked.
-
- If SPEAKFREE_LWL_TELL is defined, sfvod now forks a process and
- invokes sfspeaker with the -W option to announce the voice on demand
- server to the LWL host.
-
- Holy proliferating packets, Bitman! You mean it's possible for one
- user to publish his identity on more than one Look Who's Listening
- server? That's right, Rotten, now you can list up to five Look
- Who's Listening servers on your SPEAKFREE_LWL_TELL environment
- variable, separated by commas, and sfspeaker and sfecho will publish
- your listing on each server you name. The limit of five is not
- inherent, just intended to keep people from going off the deep end.
- In addition, the SPEAKFREE_LWL_TELL hosts can be specified by IP
- address as well as host name, for example (sh/ksh syntax):
-
- SPEAKFREE_LWL_TELL="lwl.somewhere.net,12.122.85.201,lwl.elsewhere.net"
-
- This is primarily intended to allow echo and voice on demand servers
- to advertise their existence on multiple regional LWL servers, but
- there's nothing to keep a user running sfspeaker from publishing on
- multiple sites. Supporting this required installing the multiple site
- scanning and notification code in speaker.c and echo.c, plus a small
- tweak in lwl.c so that if no SPEAKFREE_LWL_ASK variable is set and
- SPEAKFREE_LWL_TELL is used as the default, only the first server in
- the list will be queried. (Multiple-server LWL queries have their
- merits, but are better hacked in Perl than coded in C.)
-
- 8 April 1996
-
- When I added multiple LWL publication to echo.c, I inadvertently broke
- retry of failed LWL connections by echo servers. Sfspeaker gives up
- on a failed LWL host immediately (to avoid bombarding former LWL
- servers with packets), but echo servers are assumed to be more
- responsible and since they run unattended for long periods of time,
- need to be able to reconnect after an LWL server has been offline for
- a while.
-
- For the sfspeaker -d option to work with the -w (LWL only) option,
- recognition of the -d option had to be moved to pass 1 option
- processing in speaker.c.
-
- Tightened up the parsing of multiple hosts on a SPEAKFREE_LWL_TELL
- statement; spaces are now allowed before a host name, and a void entry
- no longer fools inet_addr() into returning an IP address of 0.0.0.0.
- The new code is now used by both sfspeaker and sfecho.
-
- Added a new optional compile-time definition, AUDIO_BLOCKING, not
- defined by default. If you define it, the non-Sun (i.e. Linux and
- FreeBSD) code in soundbyte.c will read from the sound card with
- blocking reads. This should help some drivers which don't handle
- non-blocking I/O.
-
- Memo to file: the half-duplex transition handshake between sfmike and
- sfspeaker assumes sfspeaker is listening on the standard INTERNET_PORT
- of 2074. If you've specified a different port with the -Pport option
- on sfspeaker, a half duplex mute request from the local host will be
- ignored.
-
- 6.1-Alpha 2 prerelease.
-
- 17 April 1996
-
- Integrated a fix from Malcolm Beattie for older versions of the C
- library on Linux which do not place the coprocessor into default IEEE
- mode. This can result in what should be harmless floating point
- underflows in lpc/lpc.c (which default IEEE handling simply rounds to
- zero, as the code intends) crashing sfspeaker with a floating point
- exception instead. Current libraries are supposed to set IEEE
- operation by defaults and not require this fix. Since I don't have a
- Linux machine to test this on, even though the fix should be harmless
- on later releases, I made the fix activated only if LINUX_FPU_FIX is
- defined at compile time. Mike.c and speaker.c now make a
- __setfpucw(_FPU_IEEE) call at initialisation time if LINUX_FPU_FIX is
- defined. I also added a comment to the Linux section of the Makefile
- describing the circumstances in which the fix should be enabled.
-
- Bradley Allen pointed out that the "#define int long" in
- lpc10/lpcdefs.h could cause an error if a subsequent system include
- file contained a "short int whatever;" declaration. This #define
- crept in during a since-abandoned attempt to get lpc10 to work on
- Windows 3.1. Since all Speak Freely for Unix platforms are 32 bit, I
- just removed the #define.
-
- Andrey A. Chernov supplied fixes for several build issues noted on
- FreeBSD. The "-static" previously used on the link flags was removed
- for FreeBSD 2.2. The little ephemeral program that the sfvod build
- process creates in order to discover the settings of AF_INET and
- SOCK_DGRAM on the current system was executed as "sfvod-t" instead of
- "./sfvod-t", as required for people who, for security reasons, don't
- have the current directory in their path. Finally, the "#define
- const" in libdes/des.h caused lots of warning messages in FreeBSD and
- keeps gcc from replacing library function calls with intrinsics. I
- made the definition of const to nothing contingent on OLDCC, as is
- already used for SunOS "cc" and other K&R-classic compilers.
-
- To help diagnose oddities in translation of DES key strings into 56
- bit DES keys, I added code to speaker.c to dump the computed DES keys
- in hex if the -d option is set. Mike.c already did this.
-
- 18 April 1996
-
- The -u output output from sflwl was identifying itself as the server
- program, not the client. Fixed in lwl.c.
-
- Some people have started sending huge strings to the sflwld servers,
- some with embedded HTML markup. These consume lots of space in the
- packets returned to requestors, and may result, for example, in not
- all the echo servers being listed. I modified lwld.c to prune the
- strings returned to in reply packets to a maximum of 48 characters
- each, dropping HTML markup, redundant white space, and attempting when
- truncation is still required, to do so at a word boundary. I also
- drop non-ISO characters which may be present. This affects only
- strings in reply packets--the full information sent by the user
- continues to appear in the HTML active users file.
-
- Feature release 6.1.
-
- 23 April 1996
-
- Integrated FreeBSD and anti-zero-divide fixes for lpc/lpc.c from
- Andrey A. Chernov, and also yet another byte-order fix which caused
- debug traces to show incorrect packet lengths when sending sound files
- on little-endian machines. I also integrated his suggestion of a
- higher initial correction in the sound file timing code for FreeBSD,
- since most machines which run it are slower than typical workstations.
-
- Added the ability for Look Who's Listening servers to talk to
- one another, forwarding packets they receive to as many as
- LWL_MAX_SITES (defined in speakfree.h as 5) other LWL servers.
- This will allow weaving the currently-isolated servers into an
- interconnected web so that regardless of which server a user queries,
- he can see users active on all servers which forward to one another.
- Here's how it works; all modifications are to lwld.c. A new
- "-f" option was added to sflwld, which accepts a comma-delimited
- list of servers (and optional port numbers, preceded by a colon).
- For example:
-
- sflwld -flwl.fourmilab.ch,lwl.somewhere.edu,lwl.elsewhere.com
-
- Any LWL packet received from a host will be forwarded to all the
- hosts named in the forward list. A forwarded packet is flagged by
- setting the 0x40 bit in the first byte, and contains four extra bytes
- at the end which give the IP address of the originating host. Packets
- forwarded from other hosts are never, themselves, forwarded: the risk
- of forwarding loops is just too great and would be too difficult
- to track down. Undoubtedly, a list of intercommunicating public
- servers will be published so operators of a new server will know
- who to forward to and how to publish the existence of their new
- server. Eventually this may be automated.
-
- In order for forwarded sites to appear on the destination host, both
- the forwarding and the destination host must be running an sflwld with
- the forwarding code present. No harm is done, however, by sending
- forwarding messages to a pre-forwarding server--they are simply
- ignored.
-
- 25 April 1996
-
- It was possible to crash a Look Who's Listening server by sending
- artfully composed bogus packets. I added an invisible Gardol shield,
- in the form of an RTCP conformance test, gardol(), in lwld.c which
- first makes sure any packet passes the basic RTCP validity checks of a
- proper header, known payload type, and length within the packet
- matching the number of bytes received (these tests are made after
- forwarded packets are transformed into regular RTCP format). In
- addition, the RTCP_SDES packet processor now checks for bogus packets
- with no CNAME item and discards them. Finally, the code that finds
- the SDES, BYE, or APP subpacket in a composite packet makes sure it
- doesn't run off the end of the packet and, if no known subpacket is
- found, discards the packet.
-
- To avoid repeated "connecting forwarding socket: Connection refused"
- messages when an LWL to which we're forwarding goes down, I changed
- forwardLwlMessage() in lwld.c to only issue the message if the -D or
- -VV options are set.
-
- The LWL packet validation code unfortunately uncovered a failure
- of the Windows version to strictly comply with the RTP spec. In
- particular, the RTCP_APP packets sent to the server to request the
- server message and to submit queries were not padded with zeroes to a
- 32 bit boundary--the packet simply terminated after the end of the
- request. I'll fix this the next time I revise the Windows version,
- but for compatibility with the installed base there's nothing for it
- but to slightly weaken the packet consistency checking to allow this
- specific case to squeak past.
-
- 28 April 1996
-
- Andrey A. Chernov pointed out that without a #include <math.h> in
- lpc10/invert.c, some compilers would incorrectly interpret the return
- type of fabs(). Fixed.
-
- 29 April 1996
-
- Plugged one more way sflwld could be tricked into aborting. If a
- connection was made with a bogus protocol ID, the accept() could
- fail, causing lwld.c's main loop to exit. I changed the behaviour
- when the accept() fails to just ignore the error and go back to the
- accept() to wait for the next connection.
-
- 2 May 1996
-
- Integrated a fix from Brian Abernathy for an undefined gethostid() in
- sfmike. Gethostid() (which is used only to build the session key) is
- emulated by a call to uname() in hp_audio.c.
-
- 9 May 1996
-
- The packet validity checking in lwld.c failed to close the accept()ed
- stream socket after rejecting an invalid packet. This meant one could
- crash sflwld by sending enough bogus packets to exhaust the maximum
- number of open file descriptors. Fixed.
-
- 29 May 1996
-
- Squashed a few more six-leggers that squirmed out during the first
- serious test of intercontinental LWL forwarding. First of all, the
- close() of the LWL socket in forwardLwlMessage() (lwld.c) was
- misplaced, orphaning a file descriptor when LWL messages were
- forwarded to more than one site, which eventually curtailed forwarding
- when all available file descriptors were consumed. Fixed.
-
- The time needed to connect() to a distant LWL server in
- forwardLwlMessage() was long enough for System V to jab its
- tried-and-true EINTR knife between our ribs. I wrapped a defensive
- do {} loop around the call to silently retry it if the alarm happens
- to ring while it's pending.
-
- If -D debugging was enabled, the "received forwarded packet from"
- message misleadingly displayed the IP address of the originating site
- rather than the forwarding server. The message now shows the server
- address, as the text strongly suggests.
-
- 24 July 1996
-
- SunOS and Solaris (but not IRIX) systems use the same underlying
- mechanism for sleep() and setitimer(). This means that a call on
- sleep() has the effect of resetting the itimer to the length of the
- sleep. This caused sfspeaker, when run with the -W ("LWL only")
- option, to transmit its LWL message every 20 minutes rather than the
- intended 10 minutes, and consequently timing out, then restarting
- repeatedly. I changed the inner loop for "-W" option mode to use
- pause() to wait for timer signals rather than sleep(120). This seems
- to have fixed things.
-
- To provide a little more slack in case a message to an LWL server is
- lost, I increased the frequency with which LWL messages are sent in
- speaker.c to one every 5 minutes. With a 15 minute timeout in sflwld,
- this means three consecutive LWL notifications must fail before a site
- will be timed out. Previously, failure to contact an LWL site in
- speaker.c caused further transmissions to that site to be abandoned
- for the duration of sfspeaker's execution. The rationale for this was
- to avoid blindly bombarding down (or former) LWL sites with packets.
- Unfortunately, this "one strike and you're out" policy could cause
- transient failures, such as inability to connect due to network
- congestion or overload on the LWL server, to shut down transmission
- and cause the site to drop off the list at the server. I modified
- speaker.c to only disable LWL transmissions after LWL_STRIKEOUT (5 by
- default) consecutive failures to contact an LWL host; with
- notification every 5 minutes, this means the host will be dropped only
- if it is down for at least 25 minutes, in which case the problem is
- unlikely to be transient.
-
- 27 July 1996
-
- On systems which support POSIX threads (pthread_xxxx), sflwld can now
- be built to run in multi-thread mode by compiling lwld.c with THREADS
- defined. This has been tested only on Solaris 2.5 so far; you can
- build a signle-thread version of sflwld as before by compiling without
- THREADS defined.
-
- Multi-thread operation not only dramatically untangles the logic of
- sflwld, it eliminates the bottleneck which could cause slow response
- on heavily-loaded servers, especially those which forward packets
- elsewhere. Previously, all requests were processed by a single
- thread, with each packet being accepted only after the previous was
- completed. This meant that a query, for example, would have to wait
- in the request queue until a previous SDES notification had been
- forwarded to all destinations. Since forwarding is often done to
- geographically remote servers, this could take a long time and have a
- cascade effect when the forwarding destination servers were themselves
- busy.
-
- With THREADS defined, each request which arrives from the socket is
- processed by its own thread, having no need to wait for anything
- related to other requests. A critical section lock protects the
- connection list from corruption due to multiple simultaneous updates,
- but this lock is set only during actual updates and scans of the list
- and never remains locked across a network or I/O operation which might
- be time consuming. Separate processes periodically scan the
- connection list to remove timed-out sites and to update the HTML list
- of active sites, if configured. For each forwarding destination a
- "forwarder" thread is created, which processes forwarding requests
- from a queue for that specific host. If the queue exceeds
- ForwarderMaxQ (currently set to 15 messages), messages to that host
- are discarded until the queue falls below that level--this keeps a
- non-responding forwarding destination from causing what amounts to a
- memory leak in sflwld. Since each destination has its own forwarder
- thread, problems in contacting one or more destinations will no longer
- affect others.
-
- Lightly-loaded servers that don't forward to remote locations will
- generally work fine without THREADS defined, but if your development
- environment supports POSIX threads, you'll obtain better performance
- for busy servers by taking advantage of multi-thread execution.
-
- 28 July 1996
-
- If the log information written by sflwld was redirected to a file
- (for example, to make a connection log), the file was written in
- block buffered mode (stdio's default handling for standard output).
- This caused individual log entries not to be written as they were
- created, but rather in large chunks every now and then. To allow
- real-time monitoring (with tail -f, for example), I added a call to
- setlinebuf(atdout) in lwld.c to guarantee that standard output is
- always line buffered, even if redirected.
-
- 2 August 1996
-
- When lwld.c was compiled for THREADS, failure to transmit a packet to
- a forwarding destination in forwarder_thread() could cause the socket
- file descriptor for the destination to be orphaned, leading, after
- sufficiently many such reverses, to failures all over the place once
- all available file handles were consumed. I changed the logic in
- forwarder_thread() guarantee the socket is always closed regardless of
- the outcome of the forwarding attempt.
-
- 8 August 1996
-
- Reduced the interval of LWL retransmission for sfecho to 5 minutes
- (LWL_RETRANSMIT in echo.c).
-
- 11 August 1996
-
- Added logic to lwld.c to plug yet another way for a remote client to
- consume resources within sflwld, eventually causing it to run out of
- file handles and go dark to the outside world. If compiled with
- THREADS, once a request was accept()ed, a socket file handle was
- allocated for the use of the service_thread. If a client connected to
- sflwld but never wrote anything to the socket, servicePacket() would
- block indefinitely on the recv() from the socket, tying up its file
- handle forever. Once enough of these zombies accumulated, accept()s
- would start to fail with out of file handles. To keep this from
- happening, I added logic in the main loop to make an entry in a linked
- list of ballOstring packets when each thread is created, recording the
- time the thread was created, its thread ID and (for debugging
- purposes), the IP address of the host where the request we're
- servicing originated. In normal cases, service_thread() dechains this
- item and releases it before exiting with pthread_exit(). If a thread
- hangs, however, timeout_thread() will, upon discovering the thread is
- still waiting for input from the requesting host ServiceThreadTimeout
- seconds (default 60) after the accept(), use pthread_kill() to send
- SIGUSR1 to the service thread. This will be caught by killserv(),
- which dechains the service thread item, closes the socket (if open),
- and exits the thread. The head of the service thread list is bshead,
- and the list is protected by the criticial section lock bsLock.
-
- This fix applies only to multi-thread versions of sflwld; it's worth
- noting that single-thread versions remain vulnerable to this form of
- hang-up, with the even more dire consequence of just ceasing to
- respond. However, given that single-thread versions have many far
- more serious problems than this, which are inherent in the code, it
- doesn't make sense trying to fix them at this time. If there is a
- population of people who want to run heavily-loaded LWL servers and
- can't get access to POSIX threads, it would make more sense to design
- a new lwld.c that used fork(), or re-architect the whole mess to run
- off inetd.
-
- 20 July (Moon Day) 1997
-
- Added an experimental implementation of jitter compensation to
- speaker.c. Jitter compensation is enabled with the -J option on
- sfspeaker. The -J option specifies, by two comma-separated numbers,
- the initial delay and length of silence which resets jitter
- compensation, both in milliseconds, with 250 milliseconds the minimum
- for each. If no idle time is specified, twice the jitter delay is
- used; if neither delay nor idle time is given, the delay is one second
- and the idle time two seconds.
-
- For example, to accumulate samples for 3 seconds before starting to
- play, and to reset the jitter timer after 4 seconds of silence, one
- would specify:
-
- sfspeaker -j3000,4000
-
- Jitter compensation is implemented by buffering samples in memory and
- only starting to play them after the jitter delay time has elapsed.
- The implementation assumes the audio output device is capable of
- buffering as many samples as will accumulate during the jitter
- delay--if it does not do this properly, jitter compensation will be
- unusable. The only alternative to requiring proper buffering in audio
- output would be a multithreaded version of sfspeaker, which would make
- it far less portable than assuming audio output buffering.
-
- Implemented a rudimentary busy signal facility in speaker.c. If the
- -B option is specified on the sfspeaker command line, only one
- connection will be accepted at a time. If another user attempts
- to connect while a connection is active, the command which follows
- the -B option will be executed to notify the caller that the
- sfspeaker user is occupied with another call. The command must
- be a C printf() format string containing a "%s" phrase at the
- point the IP address of the calling host should be inserted. If
- no command is specified, the default is equivalent to specifying:
-
- sfspeaker -b"sleep 10; sfmike %s busy.au"
-
- The "busy.au" file is a recording of the busy signal used in North
- America, with the tone repeated four times. Users should be aware
- that there is no international standard for busy signals, so if you
- communicate primarily with people in your area which uses a different
- telephone busy signal, you might want to use a recording of that tone.
-
- The ten second sleep is intended to increase the probability a
- half-duplex user will hear the busy signal after sending the
- transmission which triggers it. After a busy signal is sent to a
- caller, all packets from that host are silently discarded for an
- interval specified by busytimeout in the speaker.c source code, set to
- 60 seconds in the distribution. After that delay, additional
- connection requests from the host will be processed, resulting either
- in a connection or another busy signal.
-
- It should be observed that this busy signal implementation continues
- to rely upon the "community of reasonable people" model for which
- Speak Freely was intended. Since a connection is closed by the remote
- user "hanging up" (quitting sfmike, or closing the connection window
- in the Windows version), a "denial of service attack" is possible in
- which a malicious user connects to the victim and refuses to
- disconnect, thereby blocking other inbound calls. If you run
- sfspeaker with the -v option (as most users do), you can easily detect
- this by seeing connections rejected by busy signals while a silent
- connection remains active. Note that the three-minute inactivity
- timeout guarantees that callers whose machines crash will not block
- the receipt of other calls. If malicious refusal to disconnect
- becomes a problem, a "kill file" facility may be needed. Amateur
- radio has operated for the better part of a century on the assumption
- some bozo will not block a QSO by sending an unmodulated
- carrier--let's hope, for the moment, that Speak Freely users on the
- Internet will be at least as mature and responsible.
-
- Some implementations of make and/or shells were baffled by the
- specification of the quoted release number (Relno) definition
- in the Makefile. I moved this to a separate version.h file, in
- which the version number must appear as the last line, quoted,
- by itself. This is required so the Makefile can embed the
- version in the sfvod Perl script.
-
- 21 July 1997
-
- Swept up some lint in speaker.c.
-
- Release 6.1c.
-
- 11 April 1998
-
- The HTML active sites file created by makeHTML() in lwld.c displayed
- the time and date of the report in UTC, but the last update time in
- the local time of the site. I changed it to show all times in UTC.
-
- 12 April 1998
-
- Completed the first cut of the new conference reflector (reflect.c)
- as described in the manual page sfreflect.1.
-
- Ported the periodic client-pull refresh (-r option) code from
- reflect.c to lwld.c and added documentation to sflwld.1. I also
- included the modification to etime() in lwld.c to edit the year in the
- title as reflect.c now does.
-
- Fixed some lint quibbles in lwld.c; none were serious.
-
- Added a gimmick at the top of soundbyte.c which allows overriding the
- default name for /dev/audio and specifying different audio device
- files for input and output (the correct one is selected within
- soundinit() depending on the iomode argument). This allows Linux
- users whose drivers require opening separate /dev/audio and
- /dev/audio1 devices for full-duplex to accomplish this by adding the
- definitions:
-
- -DIN_AUDIO_DEV=\"/dev/audio\" -DOUT_AUDIO_DEV=\"/dev/audio1\"
-
- to the CCFLAGS declaration in the Makefile.
-
- Updated dependencies in the Makefile.
-
- 14 April 1998
-
- Cleaned up timeout and LWL update logic in reflect.c. The reflector
- inherited some rather confusing timing logic from the echo server,
- which needs precise timing in order to retransmit packets at the
- correct time. Since the reflector immediately retransmits any
- sound it receives, it doesn't need timing to any better than a second,
- so I ripped out all the potentially unportable microsecond logic
- and replaced it with simple calls on time() and alarm().
-
- Okay, I finally figured out a mechanism (all right, kludge) that
- permits a user to run the reflector and participate in a conference it
- is mediating all on the same machine. Here are the ugly details. The
- fundamental problem is that sfrelect has to bind the audio and control
- ports for the conference in order to receive audio from participants
- and, by doing so, blocks sfspeaker from listening to those same ports
- on the machine running sfreflect. So, while a user is free to use
- sfmike to transmit to the conference on the machine running sfreflect,
- there's no way following the usual rules to hear the audio from the
- reflector. Well, if you don't like the rules, *change them*! Enter
- the "-m" (monitor) option on sfreflect. This allows you to specify a
- host (and optional port number--the default is the usual Internet_Port
- in the Makefile, usually 2074) to which all audio received by the
- reflector is retransmitted, in addition to the conventionally
- connected hosts. If you want to reflect a conference on your machine
- and participate at the same time, proceed as follows:
-
- 1. Start sfspeaker as usual. We'll assume you use the
- standard port of 2074.
- 2. Start sfreflect specifying the -mHOST option where HOST
- is your machine's name. We'll assume you're using the
- default port of 4074 for sfreflect.
- 3. Join the conference with "sfmike HOST:4074" where HOST is
- as above.
-
- Now consider what will happen. When you send to HOST:4074, sfreflect
- will not echo that message back to HOST, as it is the originator
- (thank goodness, since that would create an infinite audio loop!), but
- will echo to the host specified by the -m option, which is the default
- port on HOST, where sfspeaker will play the audio. When others send
- audio, it will also be sent to the monitor host, so with this little
- work-around you can reflect a conference and participate without
- having two separate computers.
-
- If a monitor site is configured, the reflector also receives control
- port heartbeats from the reflector at the same time they are sent to
- connected hosts.
-
- It's ugly, but it gets you there.
-
- 15 April 1998
-
- Well, almost there. Running the reflector and joining a conference it
- is mediating on the same machine had some additional ramifications
- which needed to be addressed. First of all, consider that when sfmike
- is started, pointed at the reflector on the same machine, that will
- cause an entry to be made in the connection table pointing to the
- machine running the reflector. In the absence of a special case to
- prevent it, this will cause heartbeats to be sent back to the
- reflector itself (keeping it from timing out) and audio received from
- sites other than the reflector to be resent to the reflector itself,
- resulting in duplicate packets and stuttering audio. I added tests
- in both the heartbeat and audio reflection code to skip sending a
- packet when the destination host is the same as the host running the
- reflector.
-
- One additional tweak is required in the handling of a monitor host.
- Since we don't want to ever locally sound originating on the local
- machine (which might cause echo or feedback in the full-duplex case),
- a test is needed to avoid forwarding packets originating at the same
- IP address as the monitor host. Note that while most applications of
- the monitor host will involve the monitor host being identical to that
- running the reflector, this test is correct in the general case. If
- the reflector is running on a "headless" server with no audio hardware
- and sending monitor packets to a different workstation, we still don't
- want to reflect packets originating at that workstation back to
- itself.
-
- 16 April 1998
-
- Added a test for localhost (127.0.0.1) as an alias for the actual IP
- address of the machine running the reflector in each of the three
- places we test to avoid forwarding a packet to ourselves. I hope I've
- gotten the byte-order independence right on this test, but all the
- machines I've tested it on are big-endian.
-
- 19 April 1998
-
- The HTML status documents created by sflwld and sfreflect were
- vulnerable to unquoted HTML control sequences embedded in text
- supplied by users. While some users took advantage of this to
- include HTML links, others supplied incorrect HTML which caused some
- or all of the balance of the file to be discarded by the browser.
- I added an outHTML() function in the new file html.c which quotes all
- HTML sensitive characters as they are transcribed.
-
- 23 July 1998
-
- The lpcdecomp() function in speaker.c was using ntohl()
- instead of ntohs() to extract the uncompressed length from
- the first two bytes of buffer_val. This may be the source
- of the reports of "deafening static" by Linux users.
-
- The gsmdecomp() function in speaker.c was missing the required
- ntohs() when extracting the uncompressed length. This seems
- to have done no harm since the length was immediately fixed by
- the sanity check which follows. I added the call to avoid the
- need to be saved by the sanity check. I also extended the
- sanity check to first try a byte swap before forcing the field
- to the full packet length. This should make speaker.c accept
- either big- or little-endian values in this field.
-
- To ease the transition from prior releases with the byte
- order bug in GSM packets, I added a variant of the "-t"
- option in mike.c, "-tc", which causes the GSM length field
- to be sent correctly, in network byte order. This option
- is meaningful only on little-endian machine (since on
- big-endian machines, host and network byte order are
- identical). Specifying the -tc option allows a little-endian
- Unix host to communicate with a Windows machine or big-endian
- Unix machine running a release prior to 6.1e. In addition,
- if BYTE_SWAP_DEBUG is defined, a -td option is available which
- unconditionally swaps the bytes in the GSM length field. This
- was included solely to permit testing the compatibility code
- in speaker.c from sfmike running on a big-endian machine.
-
- Added the following message when speaker.c fails to open
- audio output in the hope of reducing the puzzlement of
- those plagued with a half-duplex /dev/audio driver:
-
- opening audio output device: No such device or address
- A common cause of this error is a sound board or
- driver which cannot run in full duplex mode (some
- boards which are physically capable of full duplex
- have drivers which cannot run them in this mode).
-
- Try uncommenting the line:
-
- DUPLEX = -DHALF_DUPLEX
-
- in the Makefile, then "make clean", then "make".
- This will operate your board in half-duplex mode
- and avoid the conflict which probably caused the
- error opening audio output.
-
- 17 September 1998
-
- Removed an extra argument to a fprintf in debug code in
- speaker.c which was spotted by the SGI C 7.2.1 compiler.
-
- Release 6.1e.
-
- 2 March 1999
-
- The two tests for robust mode packet replication in mike.c
- used lpc10comp function as the conditional for the test instead
- of the lpc10compress flag. This didn't cause any problem
- since the function name was always equivalent to TRUE and
- "robust" never gets set unless the correct flag, lpc10compress,
- is set. This error was nailed by the SGI IRIX 6.5 C compiler,
- and is now fixed to use lpc10compress.
-
- Added Blowfish as an encryption option in sfmike.c and sfspeaker.c,
- with both programs using the "-bf" option to specify the key. The
- Blowfish library is built in a new blowfish subdirectory. Blowfish is
- operated in 128 bit mode, with the actual key generated from the
- user-supplied key with the MD5 algorithm. Since the "-b" option
- was previously used by sfspeaker to specify an arbitrary busy
- signal command, I added a note to the sfspeaker manual page
- observing that in the unlikely event the first character of the
- busy signal command should be "f", one can simply quote the command
- (if not already quoted) and precede it with a space, which the shell
- will ignore.
-
- I made a slight modification to the Blowfish library to automatically
- set the BF_PTR optimisation flag in blowfish/bf_locl.h if "sparc"
- or "mips" is defined at compile time. This avoids having to set
- these flags via CFLAGS. This is only a speed optimisation; the
- code will work correctly with this variable mis-set. The code
- recommends defining BF_PTR2 for Intel machines prior to the
- Pentium Pro, again purely as a speed optimisation. I did not
- attempt to do this, since I know of no preprocessor symbol valid
- on all x86 compilers which allows detecting such processors
- unambiguously. Further, I made no attempt to use any of the
- assembly language inner loops provided with the code. Since
- Blowfish encryption and decryption is so fast (once the key has
- been generated, which only happens once per execution of sfmike
- and sfspeaker) compared to GSM, LPC, or LPC-10 compression,
- even without perfect optimisation settings Blowfish will account
- for a very small fraction of the CPU time per packet.
-
- 3 March 1999
-
- Added documentation for Blowfish encryption to the sfmike.1 and
- sfspeaker.1 manual pages and cleaned up some awkward phraseology which
- had accreted over the years.
-
- Sfvod, which works perfectly fine on Perl 4.036, failed on Perl 5.004
- in a bizarre manner which took the better part of a day to track down.
- The problem ended up being a stone bug in Perl 5.004: if a signal
- was processed while blocked in recv() waiting for a packet to arrive,
- when the next packet was received, recv() would return the null string
- for the sender's address, even through the data for the packet was
- properly stored into the string argument. I happened to notice that
- the UDP example program in "Programming Perl, 2nd ed." did not block
- on recv() but instead called select()--it had to, since it was waiting
- on multiple clients. Okay, I thought, let's use a totally unnecessary
- select() (since sfvod listens only to one socket) and see if that
- works around the bug. Damned if it didn't, and the modified code
- works on both Perl 4 and 5. I thought about using the timeout feature
- in select() to replace the existing alarm() mechanism (it would be
- safer, as &tick() would always be called in a known environment), but
- the Perl manual warns that you can't be sure select() will return
- a valid time left value on all platforms, which could potentially
- cause the timeout to be disabled due to inter-packet arrival times
- less than the tick interval.
-
- 4 March 1999
-
- I added a "text chat" feature to mike.c and speaker.c to allow people
- to send text messages while they're trying to establish a reliable
- audio link (or for any other reason). When you're running in push
- to talk mode in sfmike, pressing the period (.) key now displays a
- "Chat:" prompt, pausing audio transmission if it was in progress.
- The user can then enter a line of text in regular input mode, and
- when Return is pressed, the text is sent to all destinations on
- the control port as an RTCP APP message with type "SFtc". Upon
- receiving such a message, sfspeaker prints its content on standard
- output, prefixed with the best available information about the sender,
- in decreasing order of preference: user name, E-mail address, host
- name, and IP address.
-
- Previously, speaker.c didn't bother to decode the identity information
- in RTCP SDES packets unless the option to show connections was set.
- Since this information may be needed to identify senders of text
- chat packets, I modified it to always decode SDES packets. The
- overhead is negligible.
-
- The loop-back mode in speaker.c contained obsolete logic to compute
- packet length which resulted in its sending extra bytes at the end
- of the packet returned to the sender. This ran afoul of the packet
- length sanity check in the recipient's sfspeaker, causing the packet
- to be discarded. Fixed.
-
- For some screwball reason I can't make head or tails of, if you quit
- sfmike while in talk mode on Silicon Graphics IRIX 6.5, not only
- does Speak Freely exit but the Winterm you're running it under
- also quits, closing the window where you're running sfmike. This
- does not happen on Solaris, nor does it happen if you run sfmike
- under the SGI debugger. I've tried all the obvious things, including
- completely simulating transition back to pause mode and waiting
- 10 seconds before exiting, but at the moment the exit() is executed,
- bye-bye Winterm. Precisely the same thing happens if you run sfmike
- under xterm, or under csh or sh instead of ksh. However, if you run
- sfmike with the "-a" option (always transmit), and kill it with
- Control C in mid-transmission, everything shuts down just fine.
- Beats me. Well, after another hour of flailing around, I discovered
- that moving the fcntl(fileno(stdin), F_SETFL, 0) which sets stdin
- back into blocking I/O mode after the call to switch back to
- cooked mode rather than before fixes the disappearing shell window
- problem. Sigh. If you need to revisit this, look at function
- exiting() in mike.c.
-
- Updated sfmike.1 and sfspeaker.1 manual pages, and revised the
- introductions to each to be more generic in terminology across
- various Unix platforms.
-
- 5 March 1999
-
- Fixed a typo (actually, a blind-copy-o) in speaker.c's how-to-call
- text; in sfspeaker, the -BF option decrypts, not encrypts. (Spotted
- by RZG).
-
- Release 6.1f.
-
- 5 April 1999
-
- Fixed a harmless extra argument on the SHOW_SOCKET fprintf debug
- code in echo.c.
-
- Implemented fixes to lpc/lpc.c forwarded by Enzo Michelangeli.
- These should eliminate distortion primarily due to overflows in
- computing parameters. LPC still doesn't sound great, but it
- shouldn't break up so badly due to clipping. These fixes
- interoperate with no problems with pre-fix LPC CODECs so there's
- no problem earlier versions.
-
- 6 April 1999
-
- The current version and release date is defined in version.h, which
- was included in speakfree.h to make it available to each main program.
- This created a Makefile dependency of speakfree.h on version.h, which
- created the curious situation that if you updated version.h and did
- not modify speakfree.h, every program which included speakfree.h would
- be rebuilt on every make. I modified each program which actually
- needs the version (echo.c, lwl.c, lwld.c, mike.c, reflect.c, and
- speaker.c) to explicitly include version.h, removed the include of it
- from speakfree.h, and updated the dependencies in the Makefile to
- reflect these changes.
-
- Release 6.1g.
-
- 2 May 1999
-
- Text chat messages sent to a reflector operated by sfreflect caused it
- to crash attempting to interpret the RTCP APP message as an SDES.
- Added code to reflect.c to detect text chat packets received on the
- control port, reformat them to embed the sender's identity in the text
- area (since otherwise they'll contain only the identity of the
- reflector), and retransmit them to the control port of all connected
- hosts (and the monitoring host, if any).
-
- Added code to soundbyte.c, conditional on LINUX_DSP_SMALL_BUFFER,
- which attempts to limit the input sound buffer size to 2048 bytes.
- I have not personally tested this code and LINUX_DSP_SMALL_BUFFER
- is not defined by default.
-
- Release 6.1h.
-
- 17 May 1999
-
- Redesignated as Release 7.0 to synchronise with Windows release.
- Other than the version change, there are no changes in this release.
-
- Release 7.0.
-
- 25 August 1999
-
- Added a -w option to mike.c which dumps raw audio input to a
- binary file. This is intended to facilitate debugging of audio
- input hardware which requires special settings to produce input
- in the 8000 sample per second 8 bit mu-law encoding expected by
- sfmike.
-
- 30 August 1999
-
- Integrated code from Jean-Marc Orliaguet to support Linux (and
- other platform) audio hardware which doesn't support 8 bit
- mu-law audio. Defining LINEAR_NEEDED includes code which translates
- on the fly between 16 bit PCM and mu-law. As I have no audio hardware
- which requires this, this code has not been tested other than to
- verify that it compiles correctly when enabled.
-
- Integrated code from Jean-Marc Orliaguet to add a new "-e" option
- to sfspeaker. When a new connection is opened, the argument to
- the "-e" option is executed as a command, with the character sequence
- "%s" replaced by the hostname of the connecting hosts. One might,
- for example, answer calls automatically with:
-
- sfspeaker -e"killall sfmike >&! /dev/null; sfmike %s"
-
- 31 August 1999
-
- The half-duplex muting code which coordinates handing the
- audio device back and forth between sfmike and sfspeaker was
- unnecessarily looking up the local host's name and IP
- address, which could fail under certain bizarre circumstances.
- I modified it to use the standard local loopback address of
- 127.0.0.1 which, in the interest of paranoia, I supplied
- definitions for in mike.c and speaker.c in case some
- screwball system doesn't define it in <netinet/in.h> as it's
- supposed to.
-
- Turned off code in mike.c introduced in release 6.1e to transition
- from the incorrect GSM byte order sent by little-endian platforms
- prior to that release. To send the correct byte order, you needed
- to use the -TC option on sfmike. Now that almost everybody is
- running versions which understand the corrected byte order, this
- has been made the default. If you absolutely have to transmit to
- a Unix user running an older version on a little-endian platform,
- you can specify "-TD" to force the old, incorrect, byte order.
-
- Release 7.0b.
-
- 1 September 1999
-
- Added a test in mike.c for failure of gethostname(). If a system is
- sufficiently misconfigured that it can't obtain its own host name,
- we just call it "localhost" rather than in all likelihood crashing
- due to an uninitialised value for the host name.
-
- Removed obsolete "OLD2X" compression code in mike.c and speaker.c.
- It's not like we were going to re-enable "mumble mode" compression
- some day.
-
- Removed conditional code in mike.c based on definition of
- TINY_PACKETS. This definition has been required for years, and
- the code which predated it was obsolete and confusing in some
- places.
-
- The new files common.c and common.h, added by Jean-Marc Orliaguet
- to support the "-e" option in sfspeaker (execute command on
- connection) contained ANSI C function declaration syntax. I
- downgraded this to K&R to maintain the tradition that Speak
- Freely can be built even on ancient versions of SunOS which
- don't come with an ANSI compiler. I added a #include of common.h
- to speakfree.h, which allowed dispensing with the explicit
- (and potentially dangerous, as pointer and integers need not
- have the same length) casts in speaker.c. The code which expanded
- the reply command did not check for failure to allocate the expanded
- command and didn't release the dynamically allocated command buffer,
- creating a memory leak on each connection. Fixed.
-
- Changed des/ and idea/ from object files explicitly linked into
- sfmike and sfspeaker to libraries like the other crypto packages
- (libdes/ and blowfish/).
-
- Added the ability to build no-crypto versions of sfspeaker and sfmike
- (the only components of Speak Freely for Unix which include encryption
- code). If "NOCRYPTO" is defined at compile time, speakfree.h will not
- define the symbol "CRYPTO" on which all encryption code in mike.c and
- speaker.c is now conditional. At link time, the various encryption
- libraries will not be pulled in since no references to them appear
- in the main programs. On non-crypto builds the how-to-call
- instructions (-u option) on sfmike and sfspeaker identify themselves
- as non-crypto versions and provide the URL from which full crypto
- source code can be obtained. In addition, if the non-crypto version
- of sfspeaker receives encrypted audio, it emits a warning (once per
- connection) which explains why it is unable to decode the audio and
- again directs the user to the URL for a full crypto edition.
-
- The rationale for the non-crypto version is precisely the same as
- motivated the creation of the non-crypto Windows edition; it permits
- the creation of ready-to-run binaries for widely used platforms such
- as Linux and FreeBSD which can be freely distributed without concern
- for export controls and other regulations on encryption technology.
- Once a user installs such an edition and gets it to work transmitting
- in the clear (which one should do in any case before experimenting
- with encryption), they can then download a version with encryption
- and replace the binary they initially received.
-
- Note that non-crypto builds apply only to *binary* distributions
- of Speak Freely. Any source distribution includes all of the
- encryption modules and must be treated as cryptographic software.
-
- Integrated fixes from Walter Haidinger (walter.haidinger@gmx.at)
- to provide fine-grained control over the size and number of buffers
- used by the Linux OSS audio input driver. If LINUX_DSP_SMALL_BUFFER
- is defined, you may now also specify:
-
- FRAGMENT_BUFSIZE=32
- FRAGMENT_BUFPOWER=8
-
- which set the size of individual audio input "fragments" to
- (2 ^ FRAGMENT_BUFPOWER) and the number of fragments in the
- overall buffer FRAGMENT_BUFSIZE. Mr. Haidinger reports that the
- values given above result in about one second of audio delay with
- no lost audio on his configuration. Note that these settings have
- no effect whatsoever unless LINUX_DSP_SMALL_BUFFER is also
- defined. See the Makefile Linux configuration section for
- additional details, and the README.Linux_OSS_bufsize document for
- an in depth explanation.
-
- Integrated code from Walter Haidinger to add an "install" target
- to the Makefile. I set the default installation target directory
- tree to /usr/local. Binaries and manual pages are installed under
- root:root with permissions of 755 and 644 respectively. Note that
- you may have to edit the path for the INSTALL program at the
- top of the Makefile.
-
- Changed the default path to Perl in the Makefile to /usr/bin/perl.
- This seems more common these days that the prior setting of
- /usr/local/bin/perl.
-
- Removed some OBSOLETE-flagged code from vatpkt.c.
-
- Removed some OLDWAY-flagged code from rtpacket.c handling LPC
- compressed RTP messages.
-
- Release 7.0c.
-
- 13 September 1999
-
- Fixed a typo in a debug message related to busy signal generation
- in speaker.c.
-
- Completed the first cut of sflaunch (launch.c), which opens the
- audio device in O_RDWR mode and then executes sfmike and sfspeaker
- in two child processes, passing the audio I/O and control file
- descriptors to them with the -y# option. This allows working around
- audio device drivers which don't allow two separate programs to
- open the audio device simultaneously, even if one opens read-only
- and the other write-only. (Which remains, in my opinion, a
- stone bug. Why should audio input and output have anything to
- do with one another, necessarily, and why must both be owned
- by the same program?) Anyway, sflaunch should allow those with
- such drivers to run Speak Freely.
-
- 14 September 1999
-
- Removed a redundant definition of BUFL in soundbyte.c. It is
- defined in speakfree.h, which soundbyte.c includes.
-
- Removed the confusing SGI audio driver from the end of soundbyte.c
- and placed it in its own file, audio_sgi.c. Renamed the former
- hp_audio.c to audio_hp.c. The intent is that all future drivers
- for non-device-file audio will be named audio_something.c. Now
- each driver only contains one set of the audio interface functions.
-
- Several Speak Freely source files used the <ctype.h> functions
- such as isspace(), tolower(), but there was no include of <ctype.h>
- in speakfree.h. Fixed. (This didn't cause a problem on any known
- platform, but it generates lint natters.)
-
- In half duplex mode, mike.c did not call soundflush() on the first
- transition between Pause and Talk mode. On some platforms,
- particularly Solaris (which has a large input buffer), this
- could cause in a long transmission of sound received before
- the user made the switch to talk mode. Fixed.
-
- Release 7.0d.
-
- 15 September 1999
-
- Added g711.o to the list of object files required to build sflaunch
- when -DNEEDED_LINEAR is defined. (Fix supplied by Jean-Marc
- Orliaguet.)
-
- 18 September 1999
-
- Fixed a couple of typos and troff formatting uglies in the manual
- page sflaunch.1.
-
- Made Linux the default settings in the Makefile.
-
- The "closing audio device" debug message at the end of launch.c
- appeared even if the -d option was not specified. Fixed; I didn't
- notice this until testing on Linux since the message is only
- compiled in when AUDIO_DEVICE_FILE is defined, and I'd been
- testing on SGI, which does not define this flag.
-
- Release 7.1.
-